<div class="tutorial-bundle" data-metadata-json='{"difficulty": "medium", "groupedProjectAssets": [{"name": "space invaders", "assets": ["enemy-alien.png", "friendly-alien.png", "special-alien.png"]}]}' data-tip-sha1="1415eedfbc8fc6d6dad661d6421ad19260fc35c9"><div class="front-matter" data-complete-code-text='import pytch
import random

score = 0
lives = 3

game_over = False


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        for i in range(5):
            self.go_to_xy(-150 + i * 60, 180)
            pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while not game_over:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
            global score
            score += 10
        else:
            self.lose_life()
        self.hide()

    def lose_life(self):
        self.start_sound("scream")
        global lives
        lives -= 1
        if lives == 0:
            global game_over
            game_over = True
            pytch.broadcast("game-over")

    @pytch.when_I_receive("game-over")
    def do_game_over(self):
        self.hide()


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.show_variable(None, "score")
        pytch.show_variable(None, "lives", right=236)
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-initial-code-text="import pytch
"><h1>Blue Invaders</h1><p>In this game we'll defend ourselves from dangerous blue invaders, by
clicking on them.  But don't destroy the friendly green aliens by
mistake!</p></div><div class="chapter-content"><h2>Set the backdrop</h2><p>Our first job is to make the background for our game.  This tutorial
includes a starry sky image for us to use.  We create a sort of
<code>Stage</code>, calling it <code>Galaxy</code>, and say that it has one backdrop.  The
name in <code>""</code>s there — <code>"starry-sky.jpg"</code> — is the name of the image
file.  You can check this in the <em>Images and sounds</em> tab.</p><div class="patch-container" data-code-as-of-commit='import pytch


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
' data-slug="create-stage-with-backdrop"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>1</pre></td><td class="linenum"><pre>1</pre></td><td><pre>import pytch</pre></td></tr></tbody><tbody class="diff-add" data-added-text='

class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
'><tr><td class="linenum"></td><td class="linenum"><pre>2</pre></td><td><pre></pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>3</pre></td><td><pre></pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>4</pre></td><td><pre>class Galaxy(pytch.Stage):</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>5</pre></td><td><pre>    Backdrops = ["starry-sky.jpg"]</pre></td></tr></tbody></table></div></div><p>If you add this code to your project and click the green play button,
you should see the game's background.</p></div><div class="chapter-content"><h2>Create the aliens</h2><p>For the aliens which will drop down the screen, we are going to use a
feature of Pytch called <em>clones</em>.  These work the same way as clones
in Scratch.  There will be an <code>Alien</code> Sprite which will have two
costumes.  When a clone is wearing one costume, it counts as an enemy
space invader, and when it's wearing the other costume, it's a
friendly visitor.</p><h3>Create Sprite with costumes</h3><p>We first make the <code>Alien</code> Sprite, and say what images we want to use
for its two costumes:</p><div class="patch-container" data-code-as-of-commit='import pytch


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
' data-slug="create-alien-with-costumes"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>1</pre></td><td class="linenum"><pre>1</pre></td><td><pre>import pytch</pre></td></tr><tr><td class="linenum"><pre>2</pre></td><td class="linenum"><pre>2</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>3</pre></td><td class="linenum"><pre>3</pre></td><td><pre></pre></td></tr></tbody><tbody class="diff-add" data-added-text='class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]


'><tr><td class="linenum"></td><td class="linenum"><pre>4</pre></td><td><pre>class Alien(pytch.Sprite):</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>5</pre></td><td><pre>    Costumes = ["enemy-alien.png", "friendly-alien.png"]</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>6</pre></td><td><pre></pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>7</pre></td><td><pre></pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>4</pre></td><td class="linenum"><pre>8</pre></td><td><pre>class Galaxy(pytch.Stage):</pre></td></tr><tr><td class="linenum"><pre>5</pre></td><td class="linenum"><pre>9</pre></td><td><pre>    Backdrops = ["starry-sky.jpg"]</pre></td></tr></tbody></table></div></div><p>If you add this code to your project and run it, you should see a blue
enemy invader in the middle of the screen.  This is because Pytch
starts a Sprite off wearing the first costume in its list.</p><h3>Make the alien drift down the screen</h3><p>Next, we will make the alien move.  We'll make it glide from the top
to the bottom of the screen, then instantly go back to the top and
start gliding again.</p><p>This should all start happening as soon as the game starts, so we'll
use <code>@pytch.when_green_flag_clicked</code> at the top of the code we're
adding.  For the code itself, we want something which works the same
as Scratch's <em>forever</em> block.  In Python, we use <code>while True:</code>, and
say what we want to keep happening in <em>indented</em> lines underneath.  We
want the alien to go to the top of the screen, then glide to the
bottom.</p><div class="patch-container" data-code-as-of-commit='import pytch


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]

    @pytch.when_green_flag_clicked
    def drift_down_screen(self):
        while True:
            self.set_y(180)
            self.glide_to_xy(self.x_position, -180, 3.0)


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
' data-slug="loop-drift-down-screen"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>4</pre></td><td class="linenum"><pre>4</pre></td><td><pre>class Alien(pytch.Sprite):</pre></td></tr><tr><td class="linenum"><pre>5</pre></td><td class="linenum"><pre>5</pre></td><td><pre>    Costumes = ["enemy-alien.png", "friendly-alien.png"]</pre></td></tr><tr><td class="linenum"><pre>6</pre></td><td class="linenum"><pre>6</pre></td><td><pre></pre></td></tr></tbody><tbody class="diff-add" data-added-text="    @pytch.when_green_flag_clicked
    def drift_down_screen(self):
        while True:
            self.set_y(180)
            self.glide_to_xy(self.x_position, -180, 3.0)

"><tr><td class="linenum"></td><td class="linenum"><pre>7</pre></td><td><pre>    @pytch.when_green_flag_clicked</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>8</pre></td><td><pre>    def drift_down_screen(self):</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>9</pre></td><td><pre>        while True:</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>10</pre></td><td><pre>            self.set_y(180)</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>11</pre></td><td><pre>            self.glide_to_xy(self.x_position, -180, 3.0)</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>12</pre></td><td><pre></pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>7</pre></td><td class="linenum"><pre>13</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>8</pre></td><td class="linenum"><pre>14</pre></td><td><pre>class Galaxy(pytch.Stage):</pre></td></tr><tr><td class="linenum"><pre>9</pre></td><td class="linenum"><pre>15</pre></td><td><pre>    Backdrops = ["starry-sky.jpg"]</pre></td></tr></tbody></table></div></div><p>You'll see that the code uses <code>self.x_position</code> — this is the same as
the <em>(x position)</em> reporter block in Scratch.  For this original
alien, this might seem over-complicated, because we know its
<em>x</em>-position is zero.  But I'm looking ahead to when there will be
more than one alien, each with its own <em>x</em>-position.</p><h3>Randomly choose whether enemy or friendly</h3><p>Some of the aliens that drift down the screen will be enemies, and
some will be friendly.  Remember that this is done by making the alien
wear a different costume.</p><p>We want the costume to be random each time.  Python can generate
random numbers, but we need to say we want to use that part of Python.
We do this by <em>importing</em> the <code>random</code> library:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]

    @pytch.when_green_flag_clicked
    def drift_down_screen(self):
        while True:
            self.set_y(180)
            self.glide_to_xy(self.x_position, -180, 3.0)


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
' data-slug="import-random"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>1</pre></td><td class="linenum"><pre>1</pre></td><td><pre>import pytch</pre></td></tr></tbody><tbody class="diff-add" data-added-text="import random
"><tr><td class="linenum"></td><td class="linenum"><pre>2</pre></td><td><pre>import random</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>2</pre></td><td class="linenum"><pre>3</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>3</pre></td><td class="linenum"><pre>4</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>4</pre></td><td class="linenum"><pre>5</pre></td><td><pre>class Alien(pytch.Sprite):</pre></td></tr></tbody></table></div></div><p>This is very much like adding an extension in Scratch.</p><p>And now we can ask for a random costume.  Just like in Scratch, we can
switch costume either by giving the costume's position in the costumes
list, or by giving the costume's name.  We'll choose the costume by
position.</p><p>In Python, things in a list are numbered from <em>zero</em>, so the first
thing in a list is at 'position 0', the second thing is at
'position 1', and so on.  So we want to randomly choose either
the costume at position 0 or the one at position 1.</p><p>The <code>random.choice()</code> function will do this for us.  We want to switch
to a random costume just before jumping back to the top of the screen:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]

    @pytch.when_green_flag_clicked
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.glide_to_xy(self.x_position, -180, 3.0)


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
' data-slug="random-costume-per-descent"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>8</pre></td><td class="linenum"><pre>8</pre></td><td><pre>    @pytch.when_green_flag_clicked</pre></td></tr><tr><td class="linenum"><pre>9</pre></td><td class="linenum"><pre>9</pre></td><td><pre>    def drift_down_screen(self):</pre></td></tr><tr><td class="linenum"><pre>10</pre></td><td class="linenum"><pre>10</pre></td><td><pre>        while True:</pre></td></tr></tbody><tbody class="diff-add" data-added-text="            self.switch_costume(random.choice([0, 1]))
"><tr><td class="linenum"></td><td class="linenum"><pre>11</pre></td><td><pre>            self.switch_costume(random.choice([0, 1]))</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>11</pre></td><td class="linenum"><pre>12</pre></td><td><pre>            self.set_y(180)</pre></td></tr><tr><td class="linenum"><pre>12</pre></td><td class="linenum"><pre>13</pre></td><td><pre>            self.glide_to_xy(self.x_position, -180, 3.0)</pre></td></tr><tr><td class="linenum"><pre>13</pre></td><td class="linenum"><pre>14</pre></td><td><pre></pre></td></tr></tbody></table></div></div><p>There's quite a lot going on in this one line of new code.  We can
understand it by starting from the inside:</p><ul>
<li>
<p><code>[0, 1]</code> is a list with two things in it — the number zero and the
  number one.</p>
</li>
<li>
<p><code>random.choice([0, 1])</code> asks Python to choose randomly between the
  two things in that list.  So the result of this piece of code is
  either the number 0 or the number 1.</p>
</li>
<li>
<p><code>self.switch_costume(random.choice([0, 1]))</code> makes the Alien sprite
  switch to that randomly-chosen costume.</p>
</li>
</ul><p>If you run the project now, you should see some blue enemy invaders
and some green friendly visitors gliding down the screen.</p><p>But only one alien is on screen at a time.  We'll fix that next.</p></div><div class="chapter-content"><h2>Make lots of aliens</h2><p>To make more than one alien, we're going to use <em>clones</em>.  These work
the same as in Scratch — you get more than one copy of the same
sprite.  This is perfect for what we're trying to do.</p><p>To make sure that everything happens in the right order, we're going
to use another part of Pytch which might be familiar from Scratch —
<em>broadcasts</em>.  A sprite can 'shout' a message, and any sprite
(including the same sprite that shouted!) can be listening for that
message, and run some code whenever the sprite hears the message.</p><h3>Write code to create five clones</h3><p>We'll first write some code which clones the Alien five times.
Together with the original Alien, this will give us six aliens.  I
worked out what <em>x</em>-positions spread the aliens left to right across
the screen: -150, -90, -30, 30, 90, 150.  The idea now is to move the
original Alien to one of those places, make a clone, then move on to
the next place.  We'll make all of this happen when somebody
broadcasts the message <code>"make-clones"</code>.</p><p>This adds up to quite a lot of code:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_green_flag_clicked
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.glide_to_xy(self.x_position, -180, 3.0)


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
' data-slug="unrolled-make-clones"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>5</pre></td><td class="linenum"><pre>5</pre></td><td><pre>class Alien(pytch.Sprite):</pre></td></tr><tr><td class="linenum"><pre>6</pre></td><td class="linenum"><pre>6</pre></td><td><pre>    Costumes = ["enemy-alien.png", "friendly-alien.png"]</pre></td></tr><tr><td class="linenum"><pre>7</pre></td><td class="linenum"><pre>7</pre></td><td><pre></pre></td></tr></tbody><tbody class="diff-add" data-added-text='    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

'><tr><td class="linenum"></td><td class="linenum"><pre>8</pre></td><td><pre>    @pytch.when_I_receive("make-clones")</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>9</pre></td><td><pre>    def make_clones(self):</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>10</pre></td><td><pre>        self.go_to_xy(-150, 180)</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>11</pre></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>12</pre></td><td><pre>        self.go_to_xy(-90, 180)</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>13</pre></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>14</pre></td><td><pre>        self.go_to_xy(-30, 180)</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>15</pre></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>16</pre></td><td><pre>        self.go_to_xy(30, 180)</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>17</pre></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>18</pre></td><td><pre>        self.go_to_xy(90, 180)</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>19</pre></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>20</pre></td><td><pre>        self.go_to_xy(150, 180)</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>21</pre></td><td><pre></pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>8</pre></td><td class="linenum"><pre>22</pre></td><td><pre>    @pytch.when_green_flag_clicked</pre></td></tr><tr><td class="linenum"><pre>9</pre></td><td class="linenum"><pre>23</pre></td><td><pre>    def drift_down_screen(self):</pre></td></tr><tr><td class="linenum"><pre>10</pre></td><td class="linenum"><pre>24</pre></td><td><pre>        while True:</pre></td></tr></tbody></table></div></div><p>We'll see later how to avoid repeating ourselves like this.</p><h3>Broadcast the message to run that code</h3><p>We'll put the <em>Galaxy</em> stage in charge of broadcasting the
<code>"make-clones"</code> message.  This next bit of code needs to be added to
the <code>Galaxy</code> not the <code>Alien</code>:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_green_flag_clicked
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.glide_to_xy(self.x_position, -180, 3.0)


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.broadcast_and_wait("make-clones")
' data-slug="broadcast-make-clones"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>29</pre></td><td class="linenum"><pre>29</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>30</pre></td><td class="linenum"><pre>30</pre></td><td><pre>class Galaxy(pytch.Stage):</pre></td></tr><tr><td class="linenum"><pre>31</pre></td><td class="linenum"><pre>31</pre></td><td><pre>    Backdrops = ["starry-sky.jpg"]</pre></td></tr></tbody><tbody class="diff-add" data-added-text='
    @pytch.when_green_flag_clicked
    def run(self):
        pytch.broadcast_and_wait("make-clones")
'><tr><td class="linenum"></td><td class="linenum"><pre>32</pre></td><td><pre></pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>33</pre></td><td><pre>    @pytch.when_green_flag_clicked</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>34</pre></td><td><pre>    def run(self):</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>35</pre></td><td><pre>        pytch.broadcast_and_wait("make-clones")</pre></td></tr></tbody></table></div></div><p>If you run the game now, it doesn't really work.  We do get some more
aliens at the top of the screen, but only one of them is gliding
down.  This is because the <code>drift_down_screen()</code> code starts running
before the <code>make_clones()</code> code has finished.  We need to make sure
things happen in the right order — we'll fix this next.</p><h3>Wait for all clones to exist before gliding</h3><p>The code we just added uses <code>broadcast_and_wait()</code>.  Just like in
Scratch, your program doesn't go on to the next statement until
everybody listening for the <code>"make-clones"</code> message has finished doing
whatever it is they do when they hear it.  So if we add code after
<code>broadcast_and_wait()</code>, we know that all the clones will exist when
that code runs.</p><p>We'll use this to change when the aliens start gliding.  First, we'll
say that the <code>drift_down_screen()</code> code in the <code>Alien</code> sprite should
happen when an alien or clone hears a <code>"play-game"</code> message (and not
when the green flag is clicked).  This is like when, in Scratch, you
get rid of a script's hat block and attach a different one.</p><div class="patch-container" data-code-as-of-commit='import pytch
import random


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.glide_to_xy(self.x_position, -180, 3.0)


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.broadcast_and_wait("make-clones")
' data-slug="descend-on-play-game-broadcast"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>19</pre></td><td class="linenum"><pre>19</pre></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr><tr><td class="linenum"><pre>20</pre></td><td class="linenum"><pre>20</pre></td><td><pre>        self.go_to_xy(150, 180)</pre></td></tr><tr><td class="linenum"><pre>21</pre></td><td class="linenum"><pre>21</pre></td><td><pre></pre></td></tr></tbody><tbody class="diff-del"><tr><td class="linenum"><pre>22</pre></td><td class="linenum"></td><td><pre>    @pytch.when_green_flag_clicked</pre></td></tr></tbody><tbody class="diff-add" data-added-text='    @pytch.when_I_receive("play-game")
'><tr><td class="linenum"></td><td class="linenum"><pre>22</pre></td><td><pre>    @pytch.when_I_receive("play-game")</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>23</pre></td><td class="linenum"><pre>23</pre></td><td><pre>    def drift_down_screen(self):</pre></td></tr><tr><td class="linenum"><pre>24</pre></td><td class="linenum"><pre>24</pre></td><td><pre>        while True:</pre></td></tr><tr><td class="linenum"><pre>25</pre></td><td class="linenum"><pre>25</pre></td><td><pre>            self.switch_costume(random.choice([0, 1]))</pre></td></tr></tbody></table></div></div><p>(The red and green lines here mean that you delete the old code (red
background, with <code>-</code> at the left), and add in its place the new code
(green background, with <code>+</code> at the left).  Quite a lot of the old line
is still in the new line, so you can just delete <code>green_flag_clicked</code>
and replace it with <code>I_receive("play-game")</code> if you're careful!)</p><p>And then we'll make the <code>run()</code> code in <code>Galaxy</code> broadcast that
message, after the clones have all been created:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.glide_to_xy(self.x_position, -180, 3.0)


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")
' data-slug="broadcast-play-game"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>33</pre></td><td class="linenum"><pre>33</pre></td><td><pre>    @pytch.when_green_flag_clicked</pre></td></tr><tr><td class="linenum"><pre>34</pre></td><td class="linenum"><pre>34</pre></td><td><pre>    def run(self):</pre></td></tr><tr><td class="linenum"><pre>35</pre></td><td class="linenum"><pre>35</pre></td><td><pre>        pytch.broadcast_and_wait("make-clones")</pre></td></tr></tbody><tbody class="diff-add" data-added-text='        pytch.broadcast("play-game")
'><tr><td class="linenum"></td><td class="linenum"><pre>36</pre></td><td><pre>        pytch.broadcast("play-game")</pre></td></tr></tbody></table></div></div><p>If you run the code now, you should see waves of aliens gliding down
the screen, with a mixture of blue and green.</p><p>This is OK, but it would be better if some aliens went faster than
others.</p></div><div class="chapter-content"><h2>Randomise the glide time</h2><p>At the moment, every alien clone takes exactly 3 seconds to glide
down the screen.  We want to add a bit of variation, by making each
alien clone take a random time to glide down the screen.  This will
make some aliens move faster than others and make it more interesting.</p><p>The <code>drift_down_screen()</code> code is where we'll need to make the change.</p><p>We have already done <code>import random</code>, so we can use the
<code>random.uniform()</code> function to get a random number between 3.0 and 5.0
(including fractions).  We'll store the randomly-chosen number in a
<em>variable</em>:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, 3.0)


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")
' data-slug="define-glide-time"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>24</pre></td><td class="linenum"><pre>24</pre></td><td><pre>        while True:</pre></td></tr><tr><td class="linenum"><pre>25</pre></td><td class="linenum"><pre>25</pre></td><td><pre>            self.switch_costume(random.choice([0, 1]))</pre></td></tr><tr><td class="linenum"><pre>26</pre></td><td class="linenum"><pre>26</pre></td><td><pre>            self.set_y(180)</pre></td></tr></tbody><tbody class="diff-add" data-added-text="            glide_time = random.uniform(3.0, 5.0)
"><tr><td class="linenum"></td><td class="linenum"><pre>27</pre></td><td><pre>            glide_time = random.uniform(3.0, 5.0)</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>27</pre></td><td class="linenum"><pre>28</pre></td><td><pre>            self.glide_to_xy(self.x_position, -180, 3.0)</pre></td></tr><tr><td class="linenum"><pre>28</pre></td><td class="linenum"><pre>29</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>29</pre></td><td class="linenum"><pre>30</pre></td><td><pre></pre></td></tr></tbody></table></div></div><p>And then use this variable instead of the fixed number <code>3.0</code> in the
<code>glide_to_xy()</code> function call:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")
' data-slug="use-glide-time"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>25</pre></td><td class="linenum"><pre>25</pre></td><td><pre>            self.switch_costume(random.choice([0, 1]))</pre></td></tr><tr><td class="linenum"><pre>26</pre></td><td class="linenum"><pre>26</pre></td><td><pre>            self.set_y(180)</pre></td></tr><tr><td class="linenum"><pre>27</pre></td><td class="linenum"><pre>27</pre></td><td><pre>            glide_time = random.uniform(3.0, 5.0)</pre></td></tr></tbody><tbody class="diff-del"><tr><td class="linenum"><pre>28</pre></td><td class="linenum"></td><td><pre>            self.glide_to_xy(self.x_position, -180, 3.0)</pre></td></tr></tbody><tbody class="diff-add" data-added-text="            self.glide_to_xy(self.x_position, -180, glide_time)
"><tr><td class="linenum"></td><td class="linenum"><pre>28</pre></td><td><pre>            self.glide_to_xy(self.x_position, -180, glide_time)</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>29</pre></td><td class="linenum"><pre>29</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>30</pre></td><td class="linenum"><pre>30</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>31</pre></td><td class="linenum"><pre>31</pre></td><td><pre>class Galaxy(pytch.Stage):</pre></td></tr></tbody></table></div></div><p>Just like when we change <code>when_green_flag_clicked</code> into
<code>when_I_receive("play-game")</code> earlier, the red and green lines here
mean that you delete the old code (red background, with <code>-</code> at the
left), and add in its place the new code (green background, with <code>+</code>
at the left).  Since most of the line is the same, you can just delete
<code>3.0</code> and type in <code>glide_time</code> if you like.</p><p>Now if you run the game, som aliens should be faster than others, and
after little while it looks almost like aliens are appearing at
random.</p></div><div class="chapter-content"><h2>Click on the aliens!</h2><p>So far our project is quite nice to look at, but it isn't a <em>game</em>
because there's nothing for the player to do.  We'll fix that now.</p><h3>Add sound effects</h3><p>We want there to be sound effects when the player clicks on the alien.
We'll have one sound effect when they click on an enemy alien, and a
different one when they click on a friendly one.  This tutorial comes
with an explosion and a scream, and we tell the <code>Alien</code> sprite that we
want to use these sounds in a similar way to how we say what images we
want to use for costumes:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")
' data-slug="add-alien-sounds"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>4</pre></td><td class="linenum"><pre>4</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>5</pre></td><td class="linenum"><pre>5</pre></td><td><pre>class Alien(pytch.Sprite):</pre></td></tr><tr><td class="linenum"><pre>6</pre></td><td class="linenum"><pre>6</pre></td><td><pre>    Costumes = ["enemy-alien.png", "friendly-alien.png"]</pre></td></tr></tbody><tbody class="diff-add" data-added-text='    Sounds = ["explosion.mp3", "scream.mp3"]
'><tr><td class="linenum"></td><td class="linenum"><pre>7</pre></td><td><pre>    Sounds = ["explosion.mp3", "scream.mp3"]</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>7</pre></td><td class="linenum"><pre>8</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>8</pre></td><td class="linenum"><pre>9</pre></td><td><pre>    @pytch.when_I_receive("make-clones")</pre></td></tr><tr><td class="linenum"><pre>9</pre></td><td class="linenum"><pre>10</pre></td><td><pre>    def make_clones(self):</pre></td></tr></tbody></table></div></div><h3>React when hit</h3><p>We want the Aliens (original and clones) to react when they're clicked
on by the player.  We'll write some <code>when_this_sprite_clicked</code> code
which plays the right sound, depending on whether that clone is an
enemy or a friendly alien.</p><p>Remember that an alien is an enemy when wearing the blue costume
(number 0) and a friendly visitor when wearing the green costume
(number 1).  So we can use an <code>if</code>/<code>else</code> statement to test which
costume the alien is wearing, and play the right sound:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
        else:
            self.start_sound("scream")


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")
' data-slug="start-appropriate-sound-when-hit"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>28</pre></td><td class="linenum"><pre>28</pre></td><td><pre>            glide_time = random.uniform(3.0, 5.0)</pre></td></tr><tr><td class="linenum"><pre>29</pre></td><td class="linenum"><pre>29</pre></td><td><pre>            self.glide_to_xy(self.x_position, -180, glide_time)</pre></td></tr><tr><td class="linenum"><pre>30</pre></td><td class="linenum"><pre>30</pre></td><td><pre></pre></td></tr></tbody><tbody class="diff-add" data-added-text='    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
        else:
            self.start_sound("scream")

'><tr><td class="linenum"></td><td class="linenum"><pre>31</pre></td><td><pre>    @pytch.when_this_sprite_clicked</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>32</pre></td><td><pre>    def handle_hit(self):</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>33</pre></td><td><pre>        if self.costume_number == 0:</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>34</pre></td><td><pre>            self.start_sound("explosion")</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>35</pre></td><td><pre>        else:</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>36</pre></td><td><pre>            self.start_sound("scream")</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>37</pre></td><td><pre></pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>31</pre></td><td class="linenum"><pre>38</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>32</pre></td><td class="linenum"><pre>39</pre></td><td><pre>class Galaxy(pytch.Stage):</pre></td></tr><tr><td class="linenum"><pre>33</pre></td><td class="linenum"><pre>40</pre></td><td><pre>    Backdrops = ["starry-sky.jpg"]</pre></td></tr></tbody></table></div></div><p>If you try now, you should hear the sounds when you click on the
aliens — check you get the right sound for the right costume!</p><p>But the player can keep clicking on the same alien.  We need the alien
to hide itself once its been clicked on.  We can add a line to our
<code>handle_hit()</code> code to make this happen:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
        else:
            self.start_sound("scream")
        self.hide()


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")
' data-slug="hide-when-hit"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>34</pre></td><td class="linenum"><pre>34</pre></td><td><pre>            self.start_sound("explosion")</pre></td></tr><tr><td class="linenum"><pre>35</pre></td><td class="linenum"><pre>35</pre></td><td><pre>        else:</pre></td></tr><tr><td class="linenum"><pre>36</pre></td><td class="linenum"><pre>36</pre></td><td><pre>            self.start_sound("scream")</pre></td></tr></tbody><tbody class="diff-add" data-added-text="        self.hide()
"><tr><td class="linenum"></td><td class="linenum"><pre>37</pre></td><td><pre>        self.hide()</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>37</pre></td><td class="linenum"><pre>38</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>38</pre></td><td class="linenum"><pre>39</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>39</pre></td><td class="linenum"><pre>40</pre></td><td><pre>class Galaxy(pytch.Stage):</pre></td></tr></tbody></table></div></div><p>Now each alien should disappear (with a sound) when the player clicks
on it.  Try this!</p><p>But now we have a different problem — once the player has clicked on
all six aliens, no more aliens appear.</p><h3>Re-appear at the top of the screen</h3><p>We need to make sure each alien is visible just before it starts
gliding down the screen.  Add a line to the <code>drift_down_screen()</code> code
to make this happen:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
        else:
            self.start_sound("scream")
        self.hide()


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")
' data-slug="show-when-starting-descent"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>25</pre></td><td class="linenum"><pre>25</pre></td><td><pre>        while True:</pre></td></tr><tr><td class="linenum"><pre>26</pre></td><td class="linenum"><pre>26</pre></td><td><pre>            self.switch_costume(random.choice([0, 1]))</pre></td></tr><tr><td class="linenum"><pre>27</pre></td><td class="linenum"><pre>27</pre></td><td><pre>            self.set_y(180)</pre></td></tr></tbody><tbody class="diff-add" data-added-text="            self.show()
"><tr><td class="linenum"></td><td class="linenum"><pre>28</pre></td><td><pre>            self.show()</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>28</pre></td><td class="linenum"><pre>29</pre></td><td><pre>            glide_time = random.uniform(3.0, 5.0)</pre></td></tr><tr><td class="linenum"><pre>29</pre></td><td class="linenum"><pre>30</pre></td><td><pre>            self.glide_to_xy(self.x_position, -180, glide_time)</pre></td></tr><tr><td class="linenum"><pre>30</pre></td><td class="linenum"><pre>31</pre></td><td><pre></pre></td></tr></tbody></table></div></div><p>Try your game!  It should be quite noisy now.</p><h3>Make a sound if the player misses</h3><p>For extra noise, we'll make it so that a sound effect happens if the
player misses all the aliens when they click.  We can tell this
happens by making the <em>stage</em> react when it's clicked.</p><p>First we need to say that the <code>Galaxy</code> stage will use the 'fizz' sound
effect (which comes with this tutorial):</p><div class="patch-container" data-code-as-of-commit='import pytch
import random


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
        else:
            self.start_sound("scream")
        self.hide()


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")
' data-slug="add-sound-to-stage"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>40</pre></td><td class="linenum"><pre>40</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>41</pre></td><td class="linenum"><pre>41</pre></td><td><pre>class Galaxy(pytch.Stage):</pre></td></tr><tr><td class="linenum"><pre>42</pre></td><td class="linenum"><pre>42</pre></td><td><pre>    Backdrops = ["starry-sky.jpg"]</pre></td></tr></tbody><tbody class="diff-add" data-added-text='    Sounds = ["fizz.mp3"]
'><tr><td class="linenum"></td><td class="linenum"><pre>43</pre></td><td><pre>    Sounds = ["fizz.mp3"]</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>43</pre></td><td class="linenum"><pre>44</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>44</pre></td><td class="linenum"><pre>45</pre></td><td><pre>    @pytch.when_green_flag_clicked</pre></td></tr><tr><td class="linenum"><pre>45</pre></td><td class="linenum"><pre>46</pre></td><td><pre>    def run(self):</pre></td></tr></tbody></table></div></div><p>And then we'll add some code to the <code>Galaxy</code> so it plays this sound
when the player clicks on the stage:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
        else:
            self.start_sound("scream")
        self.hide()


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-slug="make-miss-sound-when-stage-clicked"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>46</pre></td><td class="linenum"><pre>46</pre></td><td><pre>    def run(self):</pre></td></tr><tr><td class="linenum"><pre>47</pre></td><td class="linenum"><pre>47</pre></td><td><pre>        pytch.broadcast_and_wait("make-clones")</pre></td></tr><tr><td class="linenum"><pre>48</pre></td><td class="linenum"><pre>48</pre></td><td><pre>        pytch.broadcast("play-game")</pre></td></tr></tbody><tbody class="diff-add" data-added-text='
    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
'><tr><td class="linenum"></td><td class="linenum"><pre>49</pre></td><td><pre></pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>50</pre></td><td><pre>    @pytch.when_stage_clicked</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>51</pre></td><td><pre>    def make_miss_sound(self):</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>52</pre></td><td><pre>        self.start_sound("fizz")</pre></td></tr></tbody></table></div></div><p>Try your game!  It should be even more noisy.</p></div><div class="chapter-content"><h2>Keep score</h2><p>To let the player know how they're doing, we'll add score-keeping to
the game.  Just like in Scratch, your program remembers numbers (or
strings, or lists, or anything else) using a <em>variable</em>.  In Python,
you don't have to explicitly make a variable.  Setting a new variable
to a value creates that variable for you.</p><h3>Initialise score to zero</h3><p>The player's score starts off at zero, so near the top of the program,
we'll create the <code>score</code> variable with a value of <code>0</code>:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random

score = 0


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
        else:
            self.start_sound("scream")
        self.hide()


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-slug="define-global-score"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>1</pre></td><td class="linenum"><pre>1</pre></td><td><pre>import pytch</pre></td></tr><tr><td class="linenum"><pre>2</pre></td><td class="linenum"><pre>2</pre></td><td><pre>import random</pre></td></tr><tr><td class="linenum"><pre>3</pre></td><td class="linenum"><pre>3</pre></td><td><pre></pre></td></tr></tbody><tbody class="diff-add" data-added-text="score = 0

"><tr><td class="linenum"></td><td class="linenum"><pre>4</pre></td><td><pre>score = 0</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>5</pre></td><td><pre></pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>4</pre></td><td class="linenum"><pre>6</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>5</pre></td><td class="linenum"><pre>7</pre></td><td><pre>class Alien(pytch.Sprite):</pre></td></tr><tr><td class="linenum"><pre>6</pre></td><td class="linenum"><pre>8</pre></td><td><pre>    Costumes = ["enemy-alien.png", "friendly-alien.png"]</pre></td></tr></tbody></table></div></div><h3>Show score</h3><p>In Scratch, you tick a box to say that you want the variable to be
shown.  In Pytch you do this by writing some code.  We want the
<code>score</code> variable to be shown as soon as the game starts, so the
<code>run()</code> code inside <code>Galaxy</code> is a good place to put this.</p><p>In this tutorial, we won't go into the details of what <code>None</code> means.
You can see that we give the <em>name</em> of the variable that we want to
show:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random

score = 0


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
        else:
            self.start_sound("scream")
        self.hide()


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.show_variable(None, "score")
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-slug="show-score"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>46</pre></td><td class="linenum"><pre>46</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>47</pre></td><td class="linenum"><pre>47</pre></td><td><pre>    @pytch.when_green_flag_clicked</pre></td></tr><tr><td class="linenum"><pre>48</pre></td><td class="linenum"><pre>48</pre></td><td><pre>    def run(self):</pre></td></tr></tbody><tbody class="diff-add" data-added-text='        pytch.show_variable(None, "score")
'><tr><td class="linenum"></td><td class="linenum"><pre>49</pre></td><td><pre>        pytch.show_variable(None, "score")</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>49</pre></td><td class="linenum"><pre>50</pre></td><td><pre>        pytch.broadcast_and_wait("make-clones")</pre></td></tr><tr><td class="linenum"><pre>50</pre></td><td class="linenum"><pre>51</pre></td><td><pre>        pytch.broadcast("play-game")</pre></td></tr><tr><td class="linenum"><pre>51</pre></td><td class="linenum"><pre>52</pre></td><td><pre></pre></td></tr></tbody></table></div></div><h3>Give points for hitting an enemy</h3><p>Let's give the player 10 points when they click on an enemy
invader.  We already have some code which makes a sound when the alien
is clicked, so this is a good place to add the code which updates the
score.</p><p>We need to tell Python that it's the <em>global</em> variable <code>score</code> we want
to change.  Without this, Python thinks you mean a <em>local</em> variable
which exists just inside your <code>handle_hit()</code> code.  Once we've said
which <code>score</code> we're talking about, we add 10 to it.</p><div class="patch-container" data-code-as-of-commit='import pytch
import random

score = 0


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(30, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(90, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
            global score
            score += 10
        else:
            self.start_sound("scream")
        self.hide()


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.show_variable(None, "score")
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-slug="award-score-when-hit-enemy"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>35</pre></td><td class="linenum"><pre>35</pre></td><td><pre>    def handle_hit(self):</pre></td></tr><tr><td class="linenum"><pre>36</pre></td><td class="linenum"><pre>36</pre></td><td><pre>        if self.costume_number == 0:</pre></td></tr><tr><td class="linenum"><pre>37</pre></td><td class="linenum"><pre>37</pre></td><td><pre>            self.start_sound("explosion")</pre></td></tr></tbody><tbody class="diff-add" data-added-text="            global score
            score += 10
"><tr><td class="linenum"></td><td class="linenum"><pre>38</pre></td><td><pre>            global score</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>39</pre></td><td><pre>            score += 10</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>38</pre></td><td class="linenum"><pre>40</pre></td><td><pre>        else:</pre></td></tr><tr><td class="linenum"><pre>39</pre></td><td class="linenum"><pre>41</pre></td><td><pre>            self.start_sound("scream")</pre></td></tr><tr><td class="linenum"><pre>40</pre></td><td class="linenum"><pre>42</pre></td><td><pre>        self.hide()</pre></td></tr></tbody></table></div></div><p>Try this — you should get 10 points for every blue enemy you click on.</p></div><div class="chapter-content"><h2>Avoid repetitive code</h2><p>The changes we'll make in this chapter aren't essential for the game
to work.  But they do tidy up your code and make it easier to change
and work with.</p><p>You might have thought that the code we added, quite early on, to make
the five Alien clones was very repetitive:</p><pre><code>self.go_to_xy(-150, 180)
pytch.create_clone_of(self)
self.go_to_xy(-90, 180)
pytch.create_clone_of(self)
self.go_to_xy(-30, 180)
pytch.create_clone_of(self)
self.go_to_xy(30, 180)
pytch.create_clone_of(self)
self.go_to_xy(90, 180)
pytch.create_clone_of(self)
</code></pre><p>There is a pattern to these pairs of lines of code, which we can make
clearer by writing out exactly where those <code>-90</code>, <code>-30</code>, <code>30</code>,
and <code>90</code> number come from.  The pattern is that we're adding an extra
<code>60</code> each time, starting from <code>-150</code>.  We can change the code to show
this clearly:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random

score = 0


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-150 + 60, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-150 + 2 * 60, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-150 + 3 * 60, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-150 + 4 * 60, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
            global score
            score += 10
        else:
            self.start_sound("scream")
        self.hide()


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.show_variable(None, "score")
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-slug="explicit-clone-start-locations"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>12</pre></td><td class="linenum"><pre>12</pre></td><td><pre>    def make_clones(self):</pre></td></tr><tr><td class="linenum"><pre>13</pre></td><td class="linenum"><pre>13</pre></td><td><pre>        self.go_to_xy(-150, 180)</pre></td></tr><tr><td class="linenum"><pre>14</pre></td><td class="linenum"><pre>14</pre></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr></tbody><tbody class="diff-del"><tr><td class="linenum"><pre>15</pre></td><td class="linenum"></td><td><pre>        self.go_to_xy(-90, 180)</pre></td></tr></tbody><tbody class="diff-add" data-added-text="        self.go_to_xy(-150 + 60, 180)
"><tr><td class="linenum"></td><td class="linenum"><pre>15</pre></td><td><pre>        self.go_to_xy(-150 + 60, 180)</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>16</pre></td><td class="linenum"><pre>16</pre></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr></tbody><tbody class="diff-del"><tr><td class="linenum"><pre>17</pre></td><td class="linenum"></td><td><pre>        self.go_to_xy(-30, 180)</pre></td></tr></tbody><tbody class="diff-add" data-added-text="        self.go_to_xy(-150 + 2 * 60, 180)
"><tr><td class="linenum"></td><td class="linenum"><pre>17</pre></td><td><pre>        self.go_to_xy(-150 + 2 * 60, 180)</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>18</pre></td><td class="linenum"><pre>18</pre></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr></tbody><tbody class="diff-del"><tr><td class="linenum"><pre>19</pre></td><td class="linenum"></td><td><pre>        self.go_to_xy(30, 180)</pre></td></tr></tbody><tbody class="diff-add" data-added-text="        self.go_to_xy(-150 + 3 * 60, 180)
"><tr><td class="linenum"></td><td class="linenum"><pre>19</pre></td><td><pre>        self.go_to_xy(-150 + 3 * 60, 180)</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>20</pre></td><td class="linenum"><pre>20</pre></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr></tbody><tbody class="diff-del"><tr><td class="linenum"><pre>21</pre></td><td class="linenum"></td><td><pre>        self.go_to_xy(90, 180)</pre></td></tr></tbody><tbody class="diff-add" data-added-text="        self.go_to_xy(-150 + 4 * 60, 180)
"><tr><td class="linenum"></td><td class="linenum"><pre>21</pre></td><td><pre>        self.go_to_xy(-150 + 4 * 60, 180)</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>22</pre></td><td class="linenum"><pre>22</pre></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr><tr><td class="linenum"><pre>23</pre></td><td class="linenum"><pre>23</pre></td><td><pre>        self.go_to_xy(150, 180)</pre></td></tr><tr><td class="linenum"><pre>24</pre></td><td class="linenum"><pre>24</pre></td><td><pre></pre></td></tr></tbody></table></div></div><p>and then we can even make the <code>-150</code> and <code>-90</code> values fit the exact
pattern, by changing:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random

score = 0


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        self.go_to_xy(-150 + 0 * 60, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-150 + 1 * 60, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-150 + 2 * 60, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-150 + 3 * 60, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(-150 + 4 * 60, 180)
        pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
            global score
            score += 10
        else:
            self.start_sound("scream")
        self.hide()


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.show_variable(None, "score")
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-slug="explicit-0-and-1-clone-start-locations"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>10</pre></td><td class="linenum"><pre>10</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>11</pre></td><td class="linenum"><pre>11</pre></td><td><pre>    @pytch.when_I_receive("make-clones")</pre></td></tr><tr><td class="linenum"><pre>12</pre></td><td class="linenum"><pre>12</pre></td><td><pre>    def make_clones(self):</pre></td></tr></tbody><tbody class="diff-del"><tr><td class="linenum"><pre>13</pre></td><td class="linenum"></td><td><pre>        self.go_to_xy(-150, 180)</pre></td></tr></tbody><tbody class="diff-add" data-added-text="        self.go_to_xy(-150 + 0 * 60, 180)
"><tr><td class="linenum"></td><td class="linenum"><pre>13</pre></td><td><pre>        self.go_to_xy(-150 + 0 * 60, 180)</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>14</pre></td><td class="linenum"><pre>14</pre></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr></tbody><tbody class="diff-del"><tr><td class="linenum"><pre>15</pre></td><td class="linenum"></td><td><pre>        self.go_to_xy(-150 + 60, 180)</pre></td></tr></tbody><tbody class="diff-add" data-added-text="        self.go_to_xy(-150 + 1 * 60, 180)
"><tr><td class="linenum"></td><td class="linenum"><pre>15</pre></td><td><pre>        self.go_to_xy(-150 + 1 * 60, 180)</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>16</pre></td><td class="linenum"><pre>16</pre></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr><tr><td class="linenum"><pre>17</pre></td><td class="linenum"><pre>17</pre></td><td><pre>        self.go_to_xy(-150 + 2 * 60, 180)</pre></td></tr><tr><td class="linenum"><pre>18</pre></td><td class="linenum"><pre>18</pre></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr></tbody></table></div></div><p>Now your code should look like</p><pre><code>self.go_to_xy(-150 + 0 * 60, 180)
pytch.create_clone_of(self)
self.go_to_xy(-150 + 1 * 60, 180)
pytch.create_clone_of(self)
self.go_to_xy(-150 + 2 * 60, 180)
pytch.create_clone_of(self)
self.go_to_xy(-150 + 3 * 60, 180)
pytch.create_clone_of(self)
self.go_to_xy(-150 + 4 * 60, 180)
pytch.create_clone_of(self)
</code></pre><p>and you can see that this is just five copies of</p><pre><code>self.go_to_xy(-150 + SOME_NUMBER * 60, 180)
pytch.create_clone_of(self)
</code></pre><p>with a different number in place of <code>SOME_NUMBER</code> each time, starting
at 0 and going up to 4.</p><p>We can use a <em>loop</em> to avoid all this copied code.  The <em>loop
variable</em> <code>i</code> will take on values starting at 0, and stopping
just before it gets to 5.  This "stop just before 5" way of
saying when to stop is how Python does things — it seems strange at
first but does make sense once you get used to it!</p><p>Then inside the <em>loop body</em> we have the two lines, and use the
variable <code>i</code> where the repeated code has <code>0</code>, <code>1</code>, <code>2</code>, <code>3</code>, or <code>4</code>:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random

score = 0


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        for i in range(5):
            self.go_to_xy(-150 + i * 60, 180)
            pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
            global score
            score += 10
        else:
            self.start_sound("scream")
        self.hide()


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.show_variable(None, "score")
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-slug="replace-repetition-with-loop"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>10</pre></td><td class="linenum"><pre>10</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>11</pre></td><td class="linenum"><pre>11</pre></td><td><pre>    @pytch.when_I_receive("make-clones")</pre></td></tr><tr><td class="linenum"><pre>12</pre></td><td class="linenum"><pre>12</pre></td><td><pre>    def make_clones(self):</pre></td></tr></tbody><tbody class="diff-del"><tr><td class="linenum"><pre>13</pre></td><td class="linenum"></td><td><pre>        self.go_to_xy(-150 + 0 * 60, 180)</pre></td></tr><tr><td class="linenum"><pre>14</pre></td><td class="linenum"></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr><tr><td class="linenum"><pre>15</pre></td><td class="linenum"></td><td><pre>        self.go_to_xy(-150 + 1 * 60, 180)</pre></td></tr><tr><td class="linenum"><pre>16</pre></td><td class="linenum"></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr><tr><td class="linenum"><pre>17</pre></td><td class="linenum"></td><td><pre>        self.go_to_xy(-150 + 2 * 60, 180)</pre></td></tr><tr><td class="linenum"><pre>18</pre></td><td class="linenum"></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr><tr><td class="linenum"><pre>19</pre></td><td class="linenum"></td><td><pre>        self.go_to_xy(-150 + 3 * 60, 180)</pre></td></tr><tr><td class="linenum"><pre>20</pre></td><td class="linenum"></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr><tr><td class="linenum"><pre>21</pre></td><td class="linenum"></td><td><pre>        self.go_to_xy(-150 + 4 * 60, 180)</pre></td></tr><tr><td class="linenum"><pre>22</pre></td><td class="linenum"></td><td><pre>        pytch.create_clone_of(self)</pre></td></tr></tbody><tbody class="diff-add" data-added-text="        for i in range(5):
            self.go_to_xy(-150 + i * 60, 180)
            pytch.create_clone_of(self)
"><tr><td class="linenum"></td><td class="linenum"><pre>13</pre></td><td><pre>        for i in range(5):</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>14</pre></td><td><pre>            self.go_to_xy(-150 + i * 60, 180)</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>15</pre></td><td><pre>            pytch.create_clone_of(self)</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>23</pre></td><td class="linenum"><pre>16</pre></td><td><pre>        self.go_to_xy(150, 180)</pre></td></tr><tr><td class="linenum"><pre>24</pre></td><td class="linenum"><pre>17</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>25</pre></td><td class="linenum"><pre>18</pre></td><td><pre>    @pytch.when_I_receive("play-game")</pre></td></tr></tbody></table></div></div></div><div class="chapter-content"><h2>Count lives</h2><p>The game is quite good now, but there's nothing to discourage the
player from just clicking everywhere.  There's no penalty for hitting
a friendly alien.</p><p>We'll fix that by giving the player three lives, and making it so
destroying a friendly alien costs a life.</p><h3>A 'custom block'</h3><p>In Scratch, you can create <em>custom blocks</em> to:</p><ul>
<li>
<p>give a name to a particular bit of behaviour</p>
</li>
<li>
<p>let you re-use that behaviour without duplicating large stacks of
  blocks.</p>
</li>
</ul><p>In Python, you can do the same thing.  You <em>define</em> a function, and can
<em>call</em> it from elsewhere in your code.  We'll do that to gather
together the "lose a life" behaviour.</p><p>We'll copy the existing behaviour of making the <em>scream</em> sound, by
defining a function <code>lose_life()</code>.  To define a function in Python, we
use <code>def</code> — we've been using this already in fact, to define the code
which happens when, say, the sprite is clicked on.</p><p>Here's the start of our new <code>lose_life()</code> function:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random

score = 0


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        for i in range(5):
            self.go_to_xy(-150 + i * 60, 180)
            pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
            global score
            score += 10
        else:
            self.start_sound("scream")
        self.hide()

    def lose_life(self):
        self.start_sound("scream")


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.show_variable(None, "score")
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-slug="extract-lose-life-method"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>34</pre></td><td class="linenum"><pre>34</pre></td><td><pre>            self.start_sound("scream")</pre></td></tr><tr><td class="linenum"><pre>35</pre></td><td class="linenum"><pre>35</pre></td><td><pre>        self.hide()</pre></td></tr><tr><td class="linenum"><pre>36</pre></td><td class="linenum"><pre>36</pre></td><td><pre></pre></td></tr></tbody><tbody class="diff-add" data-added-text='    def lose_life(self):
        self.start_sound("scream")

'><tr><td class="linenum"></td><td class="linenum"><pre>37</pre></td><td><pre>    def lose_life(self):</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>38</pre></td><td><pre>        self.start_sound("scream")</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>39</pre></td><td><pre></pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>37</pre></td><td class="linenum"><pre>40</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>38</pre></td><td class="linenum"><pre>41</pre></td><td><pre>class Galaxy(pytch.Stage):</pre></td></tr><tr><td class="linenum"><pre>39</pre></td><td class="linenum"><pre>42</pre></td><td><pre>    Backdrops = ["starry-sky.jpg"]</pre></td></tr></tbody></table></div></div><p>Now we have the function, but nobody is using it.  This is like the
situation in Scratch where you have made a custom block, but not used
it anywhere.</p><p>We'll change the <code>handle_hit()</code> function to use our new function:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random

score = 0


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        for i in range(5):
            self.go_to_xy(-150 + i * 60, 180)
            pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
            global score
            score += 10
        else:
            self.lose_life()
        self.hide()

    def lose_life(self):
        self.start_sound("scream")


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.show_variable(None, "score")
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-slug="call-lose-life-method"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>31</pre></td><td class="linenum"><pre>31</pre></td><td><pre>            global score</pre></td></tr><tr><td class="linenum"><pre>32</pre></td><td class="linenum"><pre>32</pre></td><td><pre>            score += 10</pre></td></tr><tr><td class="linenum"><pre>33</pre></td><td class="linenum"><pre>33</pre></td><td><pre>        else:</pre></td></tr></tbody><tbody class="diff-del"><tr><td class="linenum"><pre>34</pre></td><td class="linenum"></td><td><pre>            self.start_sound("scream")</pre></td></tr></tbody><tbody class="diff-add" data-added-text="            self.lose_life()
"><tr><td class="linenum"></td><td class="linenum"><pre>34</pre></td><td><pre>            self.lose_life()</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>35</pre></td><td class="linenum"><pre>35</pre></td><td><pre>        self.hide()</pre></td></tr><tr><td class="linenum"><pre>36</pre></td><td class="linenum"><pre>36</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>37</pre></td><td class="linenum"><pre>37</pre></td><td><pre>    def lose_life(self):</pre></td></tr></tbody></table></div></div><p>Test this now — the game should work exactly as before.  (So you might
wonder why we're making these changes.  As your projects get bigger,
it becomes more important that a human can read and understand the
program, and one way to make this easier is by giving names to parts
of the behaviour.)</p><h3>Keeping track of lives</h3><p>We need a variable to store how many lives the player has.  The
changes are very similar to when we brought in the <code>score</code> variable.
First we create the variable near the top of our program:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random

score = 0
lives = 3


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        for i in range(5):
            self.go_to_xy(-150 + i * 60, 180)
            pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
            global score
            score += 10
        else:
            self.lose_life()
        self.hide()

    def lose_life(self):
        self.start_sound("scream")


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.show_variable(None, "score")
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-slug="define-global-lives"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>2</pre></td><td class="linenum"><pre>2</pre></td><td><pre>import random</pre></td></tr><tr><td class="linenum"><pre>3</pre></td><td class="linenum"><pre>3</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>4</pre></td><td class="linenum"><pre>4</pre></td><td><pre>score = 0</pre></td></tr></tbody><tbody class="diff-add" data-added-text="lives = 3
"><tr><td class="linenum"></td><td class="linenum"><pre>5</pre></td><td><pre>lives = 3</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>5</pre></td><td class="linenum"><pre>6</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>6</pre></td><td class="linenum"><pre>7</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>7</pre></td><td class="linenum"><pre>8</pre></td><td><pre>class Alien(pytch.Sprite):</pre></td></tr></tbody></table></div></div><p>Then we want the variable to be shown on the stage.  We don't want the
display to be right on top of where the score is, so we provide extra
information saying that we want the right-hand edge of the display to
be a little bit in from the right-hand edge of the stage.  This is
what the <code>right=236</code> code is doing here:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random

score = 0
lives = 3


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        for i in range(5):
            self.go_to_xy(-150 + i * 60, 180)
            pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
            global score
            score += 10
        else:
            self.lose_life()
        self.hide()

    def lose_life(self):
        self.start_sound("scream")


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.show_variable(None, "score")
        pytch.show_variable(None, "lives", right=236)
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-slug="show-lives"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>46</pre></td><td class="linenum"><pre>46</pre></td><td><pre>    @pytch.when_green_flag_clicked</pre></td></tr><tr><td class="linenum"><pre>47</pre></td><td class="linenum"><pre>47</pre></td><td><pre>    def run(self):</pre></td></tr><tr><td class="linenum"><pre>48</pre></td><td class="linenum"><pre>48</pre></td><td><pre>        pytch.show_variable(None, "score")</pre></td></tr></tbody><tbody class="diff-add" data-added-text='        pytch.show_variable(None, "lives", right=236)
'><tr><td class="linenum"></td><td class="linenum"><pre>49</pre></td><td><pre>        pytch.show_variable(None, "lives", right=236)</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>49</pre></td><td class="linenum"><pre>50</pre></td><td><pre>        pytch.broadcast_and_wait("make-clones")</pre></td></tr><tr><td class="linenum"><pre>50</pre></td><td class="linenum"><pre>51</pre></td><td><pre>        pytch.broadcast("play-game")</pre></td></tr><tr><td class="linenum"><pre>51</pre></td><td class="linenum"><pre>52</pre></td><td><pre></pre></td></tr></tbody></table></div></div><p>And finally we then want to take one life away whenever the player
clicks on a friendly alien.  We say we want to work with the <em>global</em>
<code>lives</code> variable, and then subtract one from it:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random

score = 0
lives = 3


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        for i in range(5):
            self.go_to_xy(-150 + i * 60, 180)
            pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
            global score
            score += 10
        else:
            self.lose_life()
        self.hide()

    def lose_life(self):
        self.start_sound("scream")
        global lives
        lives -= 1


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.show_variable(None, "score")
        pytch.show_variable(None, "lives", right=236)
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-slug="decrement-lives"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>37</pre></td><td class="linenum"><pre>37</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>38</pre></td><td class="linenum"><pre>38</pre></td><td><pre>    def lose_life(self):</pre></td></tr><tr><td class="linenum"><pre>39</pre></td><td class="linenum"><pre>39</pre></td><td><pre>        self.start_sound("scream")</pre></td></tr></tbody><tbody class="diff-add" data-added-text="        global lives
        lives -= 1
"><tr><td class="linenum"></td><td class="linenum"><pre>40</pre></td><td><pre>        global lives</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>41</pre></td><td><pre>        lives -= 1</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>40</pre></td><td class="linenum"><pre>42</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>41</pre></td><td class="linenum"><pre>43</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>42</pre></td><td class="linenum"><pre>44</pre></td><td><pre>class Galaxy(pytch.Stage):</pre></td></tr></tbody></table></div></div><p>Try this now — you should see the <code>lives</code> display go down each time
you click on a green alien.  But the game doesn't stop when you run
out of lives.  We'll fix this next.</p></div><div class="chapter-content"><h2>End game when no lives left</h2><p>Our last piece of work is to make the game stop when the player has
used all their lives.  We <em>could</em> just ask 'is <code>lives</code> zero?' at
different places in the code, but it will be clearer to give a name to
this idea, with a <code>game_over</code> variable.  This will be either <code>True</code> or
<code>False</code>, and when the game starts up, the game is <em>not</em> over, so we want:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random

score = 0
lives = 3

game_over = False


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        for i in range(5):
            self.go_to_xy(-150 + i * 60, 180)
            pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
            global score
            score += 10
        else:
            self.lose_life()
        self.hide()

    def lose_life(self):
        self.start_sound("scream")
        global lives
        lives -= 1


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.show_variable(None, "score")
        pytch.show_variable(None, "lives", right=236)
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-slug="define-global-game-over"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>4</pre></td><td class="linenum"><pre>4</pre></td><td><pre>score = 0</pre></td></tr><tr><td class="linenum"><pre>5</pre></td><td class="linenum"><pre>5</pre></td><td><pre>lives = 3</pre></td></tr><tr><td class="linenum"><pre>6</pre></td><td class="linenum"><pre>6</pre></td><td><pre></pre></td></tr></tbody><tbody class="diff-add" data-added-text="game_over = False

"><tr><td class="linenum"></td><td class="linenum"><pre>7</pre></td><td><pre>game_over = False</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>8</pre></td><td><pre></pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>7</pre></td><td class="linenum"><pre>9</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>8</pre></td><td class="linenum"><pre>10</pre></td><td><pre>class Alien(pytch.Sprite):</pre></td></tr><tr><td class="linenum"><pre>9</pre></td><td class="linenum"><pre>11</pre></td><td><pre>    Costumes = ["enemy-alien.png", "friendly-alien.png"]</pre></td></tr></tbody></table></div></div><h3>All lives gone means game is over</h3><p>The only time that <code>game_over</code> might change is when the player has
lost a life.  So, inside <code>lose_life()</code>, we'll ask whether subtracting
a life has left <code>lives</code> equal to zero.  If so, we update the global
<code>game_over</code> variable to be <code>True</code>:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random

score = 0
lives = 3

game_over = False


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        for i in range(5):
            self.go_to_xy(-150 + i * 60, 180)
            pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while True:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
            global score
            score += 10
        else:
            self.lose_life()
        self.hide()

    def lose_life(self):
        self.start_sound("scream")
        global lives
        lives -= 1
        if lives == 0:
            global game_over
            game_over = True


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.show_variable(None, "score")
        pytch.show_variable(None, "lives", right=236)
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-slug="set-game-over-when-no-lives"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>41</pre></td><td class="linenum"><pre>41</pre></td><td><pre>        self.start_sound("scream")</pre></td></tr><tr><td class="linenum"><pre>42</pre></td><td class="linenum"><pre>42</pre></td><td><pre>        global lives</pre></td></tr><tr><td class="linenum"><pre>43</pre></td><td class="linenum"><pre>43</pre></td><td><pre>        lives -= 1</pre></td></tr></tbody><tbody class="diff-add" data-added-text="        if lives == 0:
            global game_over
            game_over = True
"><tr><td class="linenum"></td><td class="linenum"><pre>44</pre></td><td><pre>        if lives == 0:</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>45</pre></td><td><pre>            global game_over</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>46</pre></td><td><pre>            game_over = True</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>44</pre></td><td class="linenum"><pre>47</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>45</pre></td><td class="linenum"><pre>48</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>46</pre></td><td class="linenum"><pre>49</pre></td><td><pre>class Galaxy(pytch.Stage):</pre></td></tr></tbody></table></div></div><h3>Stop the aliens when game is over</h3><p>We now have to make sure no more aliens glide down the screen once the
game is over.  We'll change the <code>forever</code>-like loop inside
<code>drift_down_screen()</code> so that each alien (clone or original) keeps
going as long as the game is not over:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random

score = 0
lives = 3

game_over = False


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        for i in range(5):
            self.go_to_xy(-150 + i * 60, 180)
            pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while not game_over:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
            global score
            score += 10
        else:
            self.lose_life()
        self.hide()

    def lose_life(self):
        self.start_sound("scream")
        global lives
        lives -= 1
        if lives == 0:
            global game_over
            game_over = True


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.show_variable(None, "score")
        pytch.show_variable(None, "lives", right=236)
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-slug="stop-descent-loop-when-game-over"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>20</pre></td><td class="linenum"><pre>20</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>21</pre></td><td class="linenum"><pre>21</pre></td><td><pre>    @pytch.when_I_receive("play-game")</pre></td></tr><tr><td class="linenum"><pre>22</pre></td><td class="linenum"><pre>22</pre></td><td><pre>    def drift_down_screen(self):</pre></td></tr></tbody><tbody class="diff-del"><tr><td class="linenum"><pre>23</pre></td><td class="linenum"></td><td><pre>        while True:</pre></td></tr></tbody><tbody class="diff-add" data-added-text="        while not game_over:
"><tr><td class="linenum"></td><td class="linenum"><pre>23</pre></td><td><pre>        while not game_over:</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>24</pre></td><td class="linenum"><pre>24</pre></td><td><pre>            self.switch_costume(random.choice([0, 1]))</pre></td></tr><tr><td class="linenum"><pre>25</pre></td><td class="linenum"><pre>25</pre></td><td><pre>            self.set_y(180)</pre></td></tr><tr><td class="linenum"><pre>26</pre></td><td class="linenum"><pre>26</pre></td><td><pre>            self.show()</pre></td></tr></tbody></table></div></div><p>Try this now — deliberately click on three green aliens.  You should
see that no more aliens appear, but any aliens which are part-way down
the screen keep going until they reach the bottom.  We'll tidy this
last part up now.</p><p>We want all aliens to disappear immediately the game is over.  We'll
make this happen with a message which <code>lose_life()</code> will broadcast
after setting <code>game_over</code> to <code>True</code>:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random

score = 0
lives = 3

game_over = False


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        for i in range(5):
            self.go_to_xy(-150 + i * 60, 180)
            pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while not game_over:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
            global score
            score += 10
        else:
            self.lose_life()
        self.hide()

    def lose_life(self):
        self.start_sound("scream")
        global lives
        lives -= 1
        if lives == 0:
            global game_over
            game_over = True
            pytch.broadcast("game-over")


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.show_variable(None, "score")
        pytch.show_variable(None, "lives", right=236)
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-slug="broadcast-game-over"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>44</pre></td><td class="linenum"><pre>44</pre></td><td><pre>        if lives == 0:</pre></td></tr><tr><td class="linenum"><pre>45</pre></td><td class="linenum"><pre>45</pre></td><td><pre>            global game_over</pre></td></tr><tr><td class="linenum"><pre>46</pre></td><td class="linenum"><pre>46</pre></td><td><pre>            game_over = True</pre></td></tr></tbody><tbody class="diff-add" data-added-text='            pytch.broadcast("game-over")
'><tr><td class="linenum"></td><td class="linenum"><pre>47</pre></td><td><pre>            pytch.broadcast("game-over")</pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>47</pre></td><td class="linenum"><pre>48</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>48</pre></td><td class="linenum"><pre>49</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>49</pre></td><td class="linenum"><pre>50</pre></td><td><pre>class Galaxy(pytch.Stage):</pre></td></tr></tbody></table></div></div><p>If you try this now, nothing will happen because nobody is <em>listening</em>
to this message.  We'll add a last piece of code to the <code>Alien</code> so
that all aliens (clones or the original) hide when they hear that
message:</p><div class="patch-container" data-code-as-of-commit='import pytch
import random

score = 0
lives = 3

game_over = False


class Alien(pytch.Sprite):
    Costumes = ["enemy-alien.png", "friendly-alien.png"]
    Sounds = ["explosion.mp3", "scream.mp3"]

    @pytch.when_I_receive("make-clones")
    def make_clones(self):
        for i in range(5):
            self.go_to_xy(-150 + i * 60, 180)
            pytch.create_clone_of(self)
        self.go_to_xy(150, 180)

    @pytch.when_I_receive("play-game")
    def drift_down_screen(self):
        while not game_over:
            self.switch_costume(random.choice([0, 1]))
            self.set_y(180)
            self.show()
            glide_time = random.uniform(3.0, 5.0)
            self.glide_to_xy(self.x_position, -180, glide_time)

    @pytch.when_this_sprite_clicked
    def handle_hit(self):
        if self.costume_number == 0:
            self.start_sound("explosion")
            global score
            score += 10
        else:
            self.lose_life()
        self.hide()

    def lose_life(self):
        self.start_sound("scream")
        global lives
        lives -= 1
        if lives == 0:
            global game_over
            game_over = True
            pytch.broadcast("game-over")

    @pytch.when_I_receive("game-over")
    def do_game_over(self):
        self.hide()


class Galaxy(pytch.Stage):
    Backdrops = ["starry-sky.jpg"]
    Sounds = ["fizz.mp3"]

    @pytch.when_green_flag_clicked
    def run(self):
        pytch.show_variable(None, "score")
        pytch.show_variable(None, "lives", right=236)
        pytch.broadcast_and_wait("make-clones")
        pytch.broadcast("play-game")

    @pytch.when_stage_clicked
    def make_miss_sound(self):
        self.start_sound("fizz")
' data-slug="hide-when-receive-game-over"><div class="patch"><table><tbody class="diff-unch"><tr><td class="linenum"><pre>46</pre></td><td class="linenum"><pre>46</pre></td><td><pre>            game_over = True</pre></td></tr><tr><td class="linenum"><pre>47</pre></td><td class="linenum"><pre>47</pre></td><td><pre>            pytch.broadcast("game-over")</pre></td></tr><tr><td class="linenum"><pre>48</pre></td><td class="linenum"><pre>48</pre></td><td><pre></pre></td></tr></tbody><tbody class="diff-add" data-added-text='    @pytch.when_I_receive("game-over")
    def do_game_over(self):
        self.hide()

'><tr><td class="linenum"></td><td class="linenum"><pre>49</pre></td><td><pre>    @pytch.when_I_receive("game-over")</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>50</pre></td><td><pre>    def do_game_over(self):</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>51</pre></td><td><pre>        self.hide()</pre></td></tr><tr><td class="linenum"></td><td class="linenum"><pre>52</pre></td><td><pre></pre></td></tr></tbody><tbody class="diff-unch"><tr><td class="linenum"><pre>49</pre></td><td class="linenum"><pre>53</pre></td><td><pre></pre></td></tr><tr><td class="linenum"><pre>50</pre></td><td class="linenum"><pre>54</pre></td><td><pre>class Galaxy(pytch.Stage):</pre></td></tr><tr><td class="linenum"><pre>51</pre></td><td class="linenum"><pre>55</pre></td><td><pre>    Backdrops = ["starry-sky.jpg"]</pre></td></tr></tbody></table></div></div><h3>Game complete!</h3><p>Test your game now and make sure it works properly.</p></div><div class="chapter-content"><h2>Challenges</h2><p>Here are some ways you could make the game even better:</p><ul>
<li>
<p>Once the game is over, the player still hears the <em>fizz</em> noise if
  they click on the stage.  Stop this from happening.</p>
</li>
<li>
<p>Make the aliens move more quickly as the player's score goes up.</p>
</li>
<li>
<p>Add a rare red alien which is worth 50 points.</p>
</li>
<li>
<p>Add some left-to-right randomness to where the aliens start.</p>
</li>
</ul></div><div class="chapter-content"><h2>Credits</h2><p>This project was loosely inspired by the <em>Red Alert</em> game in the DK
book <a href="https://www.dk.com/us/book/9781465473615-coding-games-in-python/"><em>Coding Games in
Python</em></a>.</p><h3>Detailed credits</h3><div class="asset-credits"><p class="credit-intro">For <code class="asset-filename">starry-sky.jpg</code> (used in the project):</p><div class="credits"><p>The <a href="https://unsplash.com/photos/LUpDjlJv4_c">night sky photo</a> is
copyright Unsplash user <a href="https://unsplash.com/@andyjh07">Andy Holmes</a>,
and is used under the <a href="https://unsplash.com/license">Unsplash
licence</a>.  We have adapted the original
photo by taking an excerpt and darkening it.</p></div><p class="credit-intro">For <code class="asset-filename">enemy-alien.png</code>, <code class="asset-filename">friendly-alien.png</code> (used in the project):</p><div class="credits"><p>The two space-invader images are based on <a href="https://commons.wikimedia.org/wiki/File:Space_invaders_character_4.jpeg">"Space invaders
character
4"</a>,
which is copyright Wikimedia user アロたん.  We use it under the
<a href="https://creativecommons.org/licenses/by-sa/4.0/">Creative Commons "CC BY-SA 4.0"
licence</a>.  We have
split the original image into two, tidied up some JPEG artifacts, and
changed the colours.</p></div><p class="credit-intro">For <code class="asset-filename">explosion.mp3</code> (used in the project):</p><div class="credits"><p>The explosion sound effect is based on <a href="https://freesound.org/people/derplayer/sounds/587193/">an
original</a> by
<a href="https://freesound.org/people/derplayer/">Freesound user "derplayer"</a>,
who has placed it into the public domain.  We have trimmed it.</p></div><p class="credit-intro">For <code class="asset-filename">fizz.mp3</code> (used in the project):</p><div class="credits"><p>The fizz sound effect is based on <a href="https://freesound.org/people/odilonmarcenaro/sounds/238564/">an
original</a>
copyright <a href="https://freesound.org/people/odilonmarcenaro/">Freesound user
"odilonmarcenaro"</a>.  We
use it under the <a href="https://creativecommons.org/licenses/by/3.0/">Creative Commons CC BY 3.0
licence</a>.  We have
trimmed it and speeded it up.</p></div><p class="credit-intro">For <code class="asset-filename">scream.mp3</code> (used in the project):</p><div class="credits"><p>The scream sound effect is based on <a href="https://freesound.org/people/redafs/sounds/348310/">an
original</a>
copyright <a href="https://freesound.org/people/redafs/">Freesound user
"redafs"</a>.  We use it under the
<a href="https://creativecommons.org/licenses/by/3.0/">Creative Commons CC BY 3.0
licence</a>.  We have
trimmed it.</p></div><p class="credit-intro">For <code class="asset-filename">screenshot.png</code> (used in the tutorial text/summary):</p><div class="credits"><p>The project screenshot was created by the Pytch team.  It is a
composite of other images used in the project; see their credits for
details.</p></div><p class="credit-intro">For <code class="asset-filename">special-alien.png</code> (used in the project):</p><div class="credits"><p>The red alien image was adapted by the Pytch team from a portion of an
original image provided by the <a href="https://www.tes.com/teaching-resource/space-invaders-12297944">Times Educational
Supplement</a>.
It is used under the <a href="https://creativecommons.org/licenses/sa/1.0/">Creative Commons
Sharealike</a>
licence.  (Note that Creative Commons no longer recommends this
licence for new works, but nonetheless it is the one under which we
use this image.)</p></div></div></div></div>